In [ ]:
# import plotting libraries
%matplotlib inline
import matplotlib.pyplot as plt
In [ ]:
%load_ext nbgrader
%render_template_as solution
Write a function that returns a list of numbers, such that $x_i=i^2$, for $1\leq i \leq n$. Make sure it handles the case where $n<1$ by raising a ValueError
.
In [ ]:
def squares(n):
"""Compute the squares of numbers from 1 to n, such that the
ith element of the returned list equals i^2.
"""
{% if solution %}
if n < 1:
raise ValueError("n must be greater than or equal to 1")
return [i ** 2 for i in xrange(1, n + 1)]
{% else %}
# YOUR CODE HERE
raise NotImplementedError
{% endif %}
Your function should print [1, 4, 9, 16, 25, 36, 49, 64, 81, 100]
for $n=10$. Check that it does:
In [ ]:
squares(10)
In [ ]:
"""Check that squares returns the correct output for several inputs"""
from nbgrader.tests import assert_equal
assert_equal(squares(1), [1])
assert_equal(squares(2), [1, 4])
assert_equal(squares(10), [1, 4, 9, 16, 25, 36, 49, 64, 81, 100])
assert_equal(squares(11), [1, 4, 9, 16, 25, 36, 49, 64, 81, 100, 121])
In [ ]:
"""Check that squares raises an error for invalid inputs"""
from nbgrader.tests import assert_raises
assert_raises(ValueError, squares, 0)
assert_raises(ValueError, squares, -4)
Using your squares
function, write a function that computes the sum of the squares of the numbers from 1 to $n$. Your function should call the squares
function -- it should NOT reimplement its functionality.
In [ ]:
def sum_of_squares(n):
"""Compute the sum of the squares of numbers from 1 to n."""
{% if solution %}
return sum(squares(n))
{% else %}
# YOUR CODE HERE
raise NotImplementedError
{% endif %}
The sum of squares from 1 to 10 should be 385. Verify that this is the answer you get:
In [ ]:
sum_of_squares(10)
In [ ]:
"""Check that sum_of_squares returns the correct answer for various inputs."""
assert_equal(sum_of_squares(1), 1)
assert_equal(sum_of_squares(2), 5)
assert_equal(sum_of_squares(10), 385)
assert_equal(sum_of_squares(11), 506)
In [ ]:
"""Check that sum_of_squares relies on squares."""
orig_squares = squares
del squares
try:
assert_raises(NameError, sum_of_squares, 1)
except AssertionError:
raise AssertionError("sum_of_squares does not use squares")
finally:
squares = orig_squares
Using LaTeX math notation, write out the equation that is implemented by your sum_of_squares
function.
{% if solution %} $\sum_{i=1}^n i^2$ {% else %} YOUR ANSWER HERE {% endif %}
Create a plot of the sum of squares for $n=1$ to $n=15$. Make sure to appropriately label the $x$-axis and $y$-axis, and to give the plot a title. Set the $x$-axis limits to be 1 (minimum) and 15 (maximum).
In [ ]:
fig, ax = plt.subplots() # do not delete this line!
{% if solution %}
x = range(1, 16)
y = [sum_of_squares(x[i]) for i in xrange(len(x))]
ax.plot(x, y)
ax.set_title("Sum of squares from 1 to $n$")
ax.set_xlabel("$n$")
ax.set_ylabel("sum")
ax.set_xlim([1, 15])
{% else %}
# YOUR CODE HERE
raise NotImplementedError
{% endif %}
In [ ]:
"""Check that the axis limits are correct."""
assert_equal(ax.get_xlim(), (1.0, 15.0))
In [ ]:
"""Check that the xlabel is set."""
from nbgrader.tests import assert_unequal
assert_unequal(ax.get_xlabel(), "", "xlabel not set")
In [ ]:
"""Check that the ylabel is set."""
assert_unequal(ax.get_ylabel(), "", "ylabel not set")
In [ ]:
"""Check that the title is set."""
assert_unequal(ax.get_title(), "", "title not set")
In [ ]:
"""Check that the correct xdata was used."""
from nbgrader.tests import assert_allclose, assert_same_shape
lines = ax.get_lines()
assert_equal(len(lines), 1)
xdata = lines[0].get_xdata()
xdata_correct = np.arange(1, 16)
assert_same_shape(xdata, xdata_correct)
assert_allclose(xdata, xdata_correct)
In [ ]:
"""Check that the correct ydata was used."""
lines = ax.get_lines()
assert_equal(len(lines), 1)
xdata = lines[0].get_xdata()
ydata = lines[0].get_ydata()
ydata_correct = [sum_of_squares(x) for x in xdata]
assert_same_shape(ydata, ydata_correct)
assert_allclose(ydata, ydata_correct)